package com.lwj.springbootvue.filter;

import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import com.lwj.springbootvue.constants.HttpStatus;
import com.lwj.springbootvue.model.User;
import com.lwj.springbootvue.util.JwtUtils;
import jakarta.servlet.FilterChain;
import com.lwj.springbootvue.exception.ServiceException;
import jakarta.servlet.ServletException;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.stereotype.Component;
import org.springframework.util.StringUtils;
import org.springframework.web.filter.OncePerRequestFilter;

import java.io.IOException;


@Component
public class JwtAuthticationFilter extends OncePerRequestFilter {


    @Override
    protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain filterChain) throws ServletException, IOException {

        // 1. 判断是否为登录接口/user/login ，是   直接放行
        String uri = request.getRequestURI(); //   /user/login  直接放行

        if(uri.equals("/user/login")||uri.equals("/user/register")||uri.equals("/user/test")){
            filterChain.doFilter(request,response);// 放行
            return;
        }
        // 2. 获取token
        //获取token
        String token=request.getHeader("king-Authorization");// 前端请求头king-Authorization 携带token
        if(StrUtil.isEmpty(token)){
            throw new ServiceException(HttpStatus.UNAUTHORIZED,"token不存在！");
        }
        boolean tokenExpired = JwtUtils.isTokenExpired(token);
        if(tokenExpired){
            throw new ServiceException(HttpStatus.UNAUTHORIZED,"token已经过期请重新登录！！");
        }
        // 3.获取token中的user对象
        User tokenUser = JwtUtils.getTokenUser(token);

        if(ObjectUtil.isNull(tokenUser)){
            throw new ServiceException(HttpStatus.UNAUTHORIZED,"登录用户不存在！");
        }
        // 4. 将登录用户存在放入 springSecurity 的上下文
        UsernamePasswordAuthenticationToken Authenticate=
                new UsernamePasswordAuthenticationToken(tokenUser,null,null);
        // 将用户信息存储到SecurityContext中
        SecurityContextHolder.getContext().setAuthentication(Authenticate);

        //System.out.println("退出过滤");
        // 放行，交由后边的过滤器执行，如果没有登录，就会被登录拦截器[UsernamePasswordAuthenticationFilter]拦截到
        // /user/login  接口就不需要任何权限
        filterChain.doFilter(request,response);
    }
}
